Restore the absence entry that carries its own reason and the guard over it (#155) - #157
Merged
iderex merged 1 commit intoAug 21, 2026
Conversation
…ver it (#155) This does not finish #155. Five more of the paths that commit removed are still missing, and the question of whether a merge removing a tracked path should be refused is not touched here. What was wrong. `d3edfc95b8526033c79cb26afe48282c2c090e32` took its tree from an older state of the default branch and landed on top of a newer one, under a message describing a change to how one workflow pin is commented. Among the seven paths it replaced were both files in `internal/contexts`. The `zizmor` entry went back to giving the shared reason and naming #26 as what ends it, and `TestAPermanentAbsenceDoesNotRestOnAReasonThatEnds` went with it: git log --diff-filter=M --format='%H %s' origin/main -- internal/contexts/contexts_test.go d3edfc9 Name the version the pinned commit actually is (#151) Both blobs are the bytes that were there rather than a retyping of them: git rev-parse 90656ba:internal/contexts/contexts.go 9608b17 git hash-object internal/contexts/contexts.go 9608b17 git rev-parse 90656ba:internal/contexts/contexts_test.go 9bdd874 git hash-object internal/contexts/contexts_test.go 9bdd874 What failure this prevents is an absence written as permanent whose reason is the one that stops being true the day the required set is assembled. The guard reads `Until` and `Why` together and refuses an entry carrying both, and the near-miss it is written for is one field: emptying `Until` on an entry whose reason is still the shared one. I proved it bites by making that near-miss. With `Until` emptied on the `DCO sign-off` entry and the guard back, one test reddens and nothing else does: --- FAIL: TestAPermanentAbsenceDoesNotRestOnAReasonThatEnds (0.00s) contexts_test.go:297: the absence "DCO sign-off" is written as permanent and its reason is that the required set is empty, which is the condition that ends when the set is assembled, so the entry says the absence outlives the only thing it rests on What the absence cost is the same near-miss against what the default branch holds today, where all eleven packages run green, so nothing separated an entry resting on a debt from one that does not. Signed-off-by: Nils Lehnen <30603423+iderex@users.noreply.github.com>
iderex
deleted the
contexts/the-permanent-absence-guard-left-the-default-branch
branch
August 21, 2026 13:59
This was referenced Aug 21, 2026
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Refs #155
What this changes
internal/contexts/contexts.goandinternal/contexts/contexts_test.go, back tothe bytes the default branch held at
90656ba77a7c930d04d2205b2dd99df787853a92.Two things come back together. The
zizmorentry inAbsencescarries its ownreason again, saying that the name is created by the code-scanning upload in
zizmor.ymlrather than by the job and that the job reports under a differentstring, with
Untilempty because that absence does not end when the requiredset is assembled. And
TestAPermanentAbsenceDoesNotRestOnAReasonThatEndscomesback with it, which is the guard that refuses an entry written as permanent
whose reason is the one that stops being true.
Both are the bytes that were there rather than a retyping of them:
The means is Go in the package that already holds the entry and the suite that
already judges it, so nothing here adds a language, a runtime, a dependency or a
place to look, and the guard is testable by the suite that exists.
How the absence arrived
d3edfc95b8526033c79cb26afe48282c2c090e32took its tree from an older state ofthe default branch and landed on top of a newer one, under a message describing a
change to how one workflow pin is commented. Both files were among the seven
paths it replaced, and that commit is the only one to have touched this package
since:
Because it is the only one, taking the whole blob drops nothing that arrived
afterwards.
What failure it prevents
An absence declared permanent while resting on a reason that ends.
Untilemptysays the entry outlives the day the required set is assembled, and the shared
reason says the name is outside the set because the set has no members, which is
exactly the condition that day ends. An entry carrying both reads as settled to
whoever assembles the set.
I proved the guard bites by making the near-miss it names, which is one field:
emptying
Untilon an entry whose reason is still the shared one. With the guardrestored, that reddens one test in the tree and nothing else:
The same near-miss against what the default branch holds today, with the guard
absent, runs green in all eleven packages, so nothing there separated an entry
resting on a debt from one that does not. That is what the absence cost, measured
rather than supposed.
What was run
At
68079e9402db63c569b8f549c339e98510d08ba6, on Windows, with no graphicalsession and as an ordinary user:
go build,go vetandgofmt -leach printed nothing, which is the passingresult for all three.
No test here was skipped for needing elevation, and none was run with any.
What this does not do
It does not finish #155. Five of the six path groups that commit removed are
still missing:
LICENSEwith the## Licensesection ofREADME.md, twosections of
docs/quality-parity.md, sixteen comment lines in.github/workflows/codeql.yml, the pin comment in.github/workflows/zizmor.ymland fifteen lines of
docs/operator-guide.md.It does not touch the second question #155 raises, which is whether anything here
should refuse a merge that removes a tracked path without saying so in its body.
Restoring a file does not answer that and this change does not pretend to.
It does not move #26. The
zizmorentry's own reason and the guard over it arewhat landed for that issue and were removed; the required set on the default
branch is untouched here.
No second person has read this change. The evidence above stands in place of one,
and that is a disclosure rather than an assurance.